package util;
import static skeleton.Board.*;
public class ForbiddenChecker {
	static final int BLACK = skeleton.Startup.Chess_Clr_Black;
	static final int WHITE = skeleton.Startup.Chess_Clr_White;
	public static final int NO_FORBIDDEN = 0;
	public static final int THREE_THREE_FORBIDDEN = 1;
	public static final int FOUR_FOUR_FORBIDDEN = 2;
	public static final int LONG_FORBIDDEN = 3;
	public int four = -1, three = -1;

	private int keyPointCheck(
			int[][] board, int x, int y, int adjsame, int direction) {
		int a=-1, b=-1;
		++adjsame;
		if (direction >= 4)
			adjsame = -adjsame;
		switch (direction%4) {
		case 0:
			a = x; b = y-adjsame; break;
		case 1:
			a = x+adjsame; b = y - adjsame; break;
		case 2:
			a = x + adjsame; b = y; break;
		case 3:
			a = x + adjsame; b = y + adjsame; break;
		}
		
		board[a][b] = board[x][y] = BLACK;
		int res = forbiddenCheck(board, a, b);
		board[a][b] = board[x][y] = EMPTY;
		return res;
	}
	
	public int forbiddenCheck(int[][] board, int x, int y) {
		int[] adjsame = new int[8];
		int[] adjempty = new int[8];
		int[] jumpsame = new int[8];
		int[] jumpempty = new int[8];
		int[] jumpjumpsame = new int[8];

		for (int i=0; i<8; ++i) {
			adjsame[i] = adjempty[i] = jumpsame[i] = 0;
			jumpempty[i] = jumpjumpsame[i] = 0;
		}

		board[x][y] = BLACK;

		int _x, _y;
		int initx[] = {x, x+1, x+1, x+1, x, x-1, x-1, x-1};
		int inity[] = {y-1, y-1, y, y+1, y+1, y+1, y, y-1};
		int incx[] = {0, 1, 1, 1, 0, -1, -1, -1};
		int incy[] = {-1, -1, 0, 1, 1, 1, 0, -1};
		for (int i=0; i<8; ++i) {
			_x = initx[i]; _y=inity[i];
			for (;_x<LEN&&_x>=0&&_y<LEN&&_y>=0&&board[_x][_y]==BLACK; 
				_x+=incx[i],_y+=incy[i],++adjsame[i]);
			for (;_x<LEN&&_x>=0&&_y<LEN&&_y>=0&&board[_x][_y]==EMPTY;
				_x+=incx[i],_y+=incy[i],++adjempty[i]);
			for (;_x<LEN&&_x>=0&&_y<LEN&&_y>=0&&board[_x][_y]==BLACK;
				_x+=incx[i],_y+=incy[i],++jumpsame[i]);
			for (;_x<LEN&&_x>=0&&_y<LEN&&_y>=0&&board[_x][_y]==EMPTY;
				_x+=incx[i],_y+=incy[i],++jumpempty[i]);
			for (;_x<LEN&&_x>=0&&_y<LEN&&_y>=0&&board[_x][_y]==BLACK;
				_x+=incx[i],_y+=incy[i],++jumpjumpsame[i]); 
		}
		
		board[x][y] = EMPTY;
		
		int fourCount = 0, threeCount = 0;
		
		for (int i=0; i<4; ++i)
			if (adjsame[i] + adjsame[i+4] == 4) return NO_FORBIDDEN;
		
		for (int i=0; i<4; ++i) {
			if (adjsame[i] + adjsame[i+4] >= 5)
				return LONG_FORBIDDEN;
			else if (adjsame[i] + adjsame[i+4] == 3) { //?0000?
				boolean isFour = false;
				if (adjempty[i] > 0)  //?+0000?
					if (keyPointCheck(board, x, y, adjsame[i], i) == NO_FORBIDDEN)
						isFour = true;
				if (adjempty[i+4] > 0) //?0000+?
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4) == NO_FORBIDDEN)
						isFour = true;
				if (isFour)
					++fourCount;
			}
			else if (adjsame[i] + adjsame[i+4] == 2) { //?000?
				if (adjempty[i] == 1 && jumpsame[i] == 1) //?0+000?
					if (keyPointCheck(board, x, y, adjsame[i],i) == NO_FORBIDDEN)
						++fourCount;
				if (adjempty[i+4] == 1 && jumpsame[i+4] == 1)//?000+0?
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4) == NO_FORBIDDEN)
						++fourCount;
				
				boolean isThree = false;
				//?++000+?
				if ((adjempty[i] > 2 || adjempty[i] == 2 && jumpsame[i] == 0) &&
						(adjempty[i+4]>1||adjempty[i+4]==1&&jumpsame[i+4]==0))
					if (keyPointCheck(board, x, y, adjsame[i], i) == NO_FORBIDDEN)
						isThree = true;
				//?+000++?
				if ((adjempty[i+4]>2||adjempty[i+4]==2&&jumpsame[i+4]==0)&&
						(adjempty[i]>1||adjempty[i]==1&&jumpsame[i]==0))
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4) == NO_FORBIDDEN)
						isThree = true;
				if (isThree)
					++threeCount;
			}
			else if (adjsame[i] + adjsame[i+4] == 1) { //?00?
				if (adjempty[i] == 1 && jumpsame[i] == 2) //?00+00?
					if (keyPointCheck(board, x, y, adjsame[i], i) ==NO_FORBIDDEN)
						++fourCount;
				if (adjempty[i+4]==1 && jumpsame[i+4]==2) //?00+00?
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4) == NO_FORBIDDEN)
						++fourCount;
				if (adjempty[i]==1 && jumpsame[i]==1 && ////?+00+0+?
						(jumpempty[i]>1||jumpempty[i]==1&&jumpjumpsame[i]==0) &&
						(adjempty[i+4]>1||adjempty[i+4]==1&&jumpsame[i+4]==0))
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4)==NO_FORBIDDEN)
						++threeCount;
			}
			else if (adjsame[i]+adjsame[i+4]==0) { //?0?
				if (adjempty[i]==1 && jumpsame[i]==3) //?000+0? 
					if (keyPointCheck(board, x, y, adjsame[i], i) == NO_FORBIDDEN)
						++fourCount;
				if (adjempty[i+4]==1 && jumpsame[i+4]==3) //0+000
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4) == NO_FORBIDDEN)
						++fourCount;
				if (adjempty[i]==1 && jumpsame[i]==2 && //?+00+0+?
						(jumpempty[i]>1 || jumpempty[i]==1&&jumpjumpsame[i]==0)&&
						(adjempty[i+4]>1||adjempty[i+4]==1&&jumpsame[i+4]==0))
					if (keyPointCheck(board, x, y, adjsame[i], i) == NO_FORBIDDEN)
						++threeCount;
				if (adjempty[i+4]==1 && jumpsame[i+4]==2 && //?+0+00+? 
						(jumpempty[i+4]>1||jumpempty[i+4]==1&&jumpjumpsame[i+4]==0)&&
						(adjempty[i]>1||adjempty[i]==1&&jumpsame[i]==0))
					if (keyPointCheck(board, x, y, adjsame[i+4], i+4) == NO_FORBIDDEN)
						++threeCount;
			}
		}
		
		four = fourCount;
		three = threeCount;
		if (fourCount > 1)
			return FOUR_FOUR_FORBIDDEN;
		if (threeCount > 1)
			return THREE_THREE_FORBIDDEN;
		return NO_FORBIDDEN;
	}
	
}